import ejs from 'ejs';
import path from 'path';
import { useDesignStore, type CanvasComponent } from '@/stores/designStore';
import { ElMessage } from 'element-plus'; // Assuming we might show messages

// Export the interface
export interface ExportedFile {
  relativePath: string; // e.g., 'src/components/MainWindow.vue'
  content: string;
}

// Define and Export component import paths (adjust as necessary)
export const componentImportMap: Record<string, { importPath: string }> = {
    'el-button': { importPath: 'element-plus/es/components/button/index.mjs' },
    'el-input': { importPath: 'element-plus/es/components/input/index.mjs' },
    'el-select': { importPath: 'element-plus/es/components/select/index.mjs' },
    'el-option': { importPath: 'element-plus/es/components/option/index.mjs' },
    'el-radio-group': { importPath: 'element-plus/es/components/radio-group/index.mjs' },
    'el-radio-button': { importPath: 'element-plus/es/components/radio-button/index.mjs' },
    'el-checkbox-group': { importPath: 'element-plus/es/components/checkbox-group/index.mjs' },
    'el-checkbox': { importPath: 'element-plus/es/components/checkbox/index.mjs' },
    'el-row': { importPath: 'element-plus/es/components/row/index.mjs' },
    'el-col': { importPath: 'element-plus/es/components/col/index.mjs' },
    'el-switch': { importPath: 'element-plus/es/components/switch/index.mjs' },
    'el-progress': { importPath: 'element-plus/es/components/progress/index.mjs' },
    'el-image': { importPath: 'element-plus/es/components/image/index.mjs' },
    'el-form': { importPath: 'element-plus/es/components/form/index.mjs' },
    'el-form-item': { importPath: 'element-plus/es/components/form-item/index.mjs' },
    'el-table': { importPath: 'element-plus/es/components/table/index.mjs' },
    'el-table-column': { importPath: 'element-plus/es/components/table-column/index.mjs' },
    'el-radio': { importPath: 'element-plus/es/components/radio/index.mjs' },
    'el-date-picker': { importPath: 'element-plus/es/components/date-picker/index.mjs' },
    'el-time-picker': { importPath: 'element-plus/es/components/time-picker/index.mjs' },
    'el-slider': { importPath: 'element-plus/es/components/slider/index.mjs' },
    'el-cascader': { importPath: 'element-plus/es/components/cascader/index.mjs' },
    'el-color-picker': { importPath: 'element-plus/es/components/color-picker/index.mjs' },
    'el-transfer': { importPath: 'element-plus/es/components/transfer/index.mjs' },
    'el-rate': { importPath: 'element-plus/es/components/rate/index.mjs' },
    'el-divider': { importPath: 'element-plus/es/components/divider/index.mjs' },
    'el-tag': { importPath: 'element-plus/es/components/tag/index.mjs' },
    'el-card': { importPath: 'element-plus/es/components/card/index.mjs' },
    'el-alert': { importPath: 'element-plus/es/components/alert/index.mjs' },
    'el-dropdown': { importPath: 'element-plus/es/components/dropdown/index.mjs' },
    'el-dropdown-item': { importPath: 'element-plus/es/components/dropdown-item/index.mjs' },
    'el-menu': { importPath: 'element-plus/es/components/menu/index.mjs' },
    'el-menu-item': { importPath: 'element-plus/es/components/menu-item/index.mjs' },
    'el-submenu': { importPath: 'element-plus/es/components/submenu/index.mjs' },
    'el-tabs': { importPath: 'element-plus/es/components/tabs/index.mjs' },
    'el-tab-pane': { importPath: 'element-plus/es/components/tab-pane/index.mjs' },
    'el-breadcrumb': { importPath: 'element-plus/es/components/breadcrumb/index.mjs' },
    'el-breadcrumb-item': { importPath: 'element-plus/es/components/breadcrumb-item/index.mjs' },
    'el-page-header': { importPath: 'element-plus/es/components/page-header/index.mjs' },
    'el-steps': { importPath: 'element-plus/es/components/steps/index.mjs' },
    'el-step': { importPath: 'element-plus/es/components/step/index.mjs' },
    'el-pagination': { importPath: 'element-plus/es/components/pagination/index.mjs' },
    'el-badge': { importPath: 'element-plus/es/components/badge/index.mjs' },
    'el-avatar': { importPath: 'element-plus/es/components/avatar/index.mjs' },
    'el-skeleton': { importPath: 'element-plus/es/components/skeleton/index.mjs' },
    'el-skeleton-item': { importPath: 'element-plus/es/components/skeleton-item/index.mjs' },
    'el-empty': { importPath: 'element-plus/es/components/empty/index.mjs' },
    'el-descriptions': { importPath: 'element-plus/es/components/descriptions/index.mjs' },
    'el-descriptions-item': { importPath: 'element-plus/es/components/descriptions-item/index.mjs' },
    'el-result': { importPath: 'element-plus/es/components/result/index.mjs' },
    'el-calendar': { importPath: 'element-plus/es/components/calendar/index.mjs' },
    'el-timeline': { importPath: 'element-plus/es/components/timeline/index.mjs' },
    'el-timeline-item': { importPath: 'element-plus/es/components/timeline-item/index.mjs' },
    'el-link': { importPath: 'element-plus/es/components/link/index.mjs' },
    'el-dialog': { importPath: 'element-plus/es/components/dialog/index.mjs' },
    'el-tooltip': { importPath: 'element-plus/es/components/tooltip/index.mjs' },
    'el-popover': { importPath: 'element-plus/es/components/popover/index.mjs' },
    'el-popconfirm': { importPath: 'element-plus/es/components/popconfirm/index.mjs' },
    'el-drawer': { importPath: 'element-plus/es/components/drawer/index.mjs' },
    'el-scrollbar': { importPath: 'element-plus/es/components/scrollbar/index.mjs' },
    'el-backtop': { importPath: 'element-plus/es/components/backtop/index.mjs' },
    'div': { importPath: '' },
    'span': { importPath: '' },
};

/**
 * Recursively traverses the component tree to find all unique component types used.
 */
function getComponentUsage(components: CanvasComponent[]): Record<string, { importPath: string }> {
    const usage: Record<string, { importPath: string }> = {};
    const traverse = (comps: CanvasComponent[]) => {
        comps.forEach(comp => {
            if (componentImportMap[comp.type] && componentImportMap[comp.type].importPath) {
                usage[comp.type] = componentImportMap[comp.type];
            }
            if (comp.children && comp.children.length > 0) {
                traverse(comp.children);
            }
        });
    };
    traverse(components);
    return usage;
}

/**
 * Prepares the component data for export.
 * - Removes internal properties (like parentId, isSelected).
 * - Serializes styles (potentially, or keep as object if template handles it).
 * - Handles event references.
 */
function prepareComponentsForExport(components: CanvasComponent[]): any[] {
    return components.map(comp => {
        const exportedComp: any = {
            id: comp.id,
            type: comp.type,
            props: { ...comp.props }, // 正确复制props
            style: { ...comp.style }, // 复制style
            events: { ...comp.events } // 复制事件
        };
        
        // 对于按钮组件，确保props中包含label或text
        if (comp.type === 'el-button') {
            // 如果按钮没有文本，使用默认值
            if (!exportedComp.props.text && !exportedComp.props.label) {
                if (comp.children && comp.children.length > 0 && typeof comp.children[0] === 'string') {
                    // 如果子元素是文本，使用它作为按钮文本
                    exportedComp.props.text = comp.children[0];
                } else {
                    // 否则使用默认文本
                    exportedComp.props.text = '按钮';
                }
            }
        }
        
        // 递归处理子组件
        if (comp.children && comp.children.length > 0) {
            exportedComp.children = prepareComponentsForExport(comp.children);
        }
        
        // 移除可能存在的大型或循环引用
        delete exportedComp.props.ref; // 示例
        
        return exportedComp;
    });
}

// Define the structure for the data needed by the main process
export interface ProjectExportData {
    viewData: {
        components: any[];
        componentUsage: Record<string, { importPath: string }>;
        globalStyles: string; // Placeholder for now
        projectName: string;
        productName: string;
        windowWidth: number;
        windowHeight: number;
        elementPlusStyles: string;
        elementPlusRuntime: string;
        vueRuntime: string;
        componentStyles: string;
        appScript: string;
    };
    templatesToRender: Array<{ template: string; output: string }>;
    canvasSize: { width: number; height: number };
}

/**
 * Prepares the data needed for project export (source or build).
 */
export function prepareProjectExportData(): ProjectExportData {
    const designStore = useDesignStore();

    const preparedComponents = prepareComponentsForExport(designStore.canvasComponents);
    const componentUsage = getComponentUsage(preparedComponents);
    
    // 使用占位符或模拟函数
    const globalStyles = '/* Global styles placeholder */';
    const elementPlusStyles = '/* ElementPlus styles will be loaded at runtime */';
    const elementPlusRuntime = '/* ElementPlus runtime will be loaded at runtime */';
    const vueRuntime = '/* Vue runtime will be loaded at runtime */';

    // 新增 UI 相关选项
    const {
        windowWidth = 1024,
        windowHeight = 768,
        projectName = 'EasyWindowProject',
        productName = 'Easy Window UI'
    } = {} as any;  // 未来可以从配置中读取
    
    const componentStyles = generateComponentStyles(preparedComponents);
    const appScript = '/* App script will be generated at runtime */';

    return {
        viewData: {
            components: preparedComponents,
            componentUsage,
            globalStyles,
            projectName,
            productName,
            windowWidth,
            windowHeight,
            elementPlusStyles,
            elementPlusRuntime,
            vueRuntime,
            componentStyles,
            appScript
        },
        templatesToRender: [
            // 原 renderable 模板
            { template: 'vite.config.js.ejs', output: 'vite.config.js' },
            { template: 'package.json.ejs', output: 'package.json' },
            { template: 'index.html.ejs', output: 'index.html' },
            { template: 'main.js.ejs', output: 'src/main.js' },
            { template: 'App.vue.ejs', output: 'src/App.vue' },
            { template: 'assets/main.css.ejs', output: 'src/assets/main.css' },
            { template: 'components/MainUI.vue.ejs', output: 'src/components/MainUI.vue' }
        ],
        canvasSize: designStore.canvasSize // 添加画布尺寸
    };
}

/**
 * 为组件生成特定样式
 */
function generateComponentStyles(components: any[]): string {
    let styles = '';
    
    // 递归处理组件样式
    const processComponentStyles = (comps: any[], prefix = '') => {
        comps.forEach((comp, index) => {
            // 组件选择器
            const selector = `${prefix}[data-component-id="${comp.id}"]`;
            
            // 特定组件类型的样式
            if (comp.type === 'el-button') {
                styles += `
${selector} {
    display: inline-flex;
    align-items: center;
    justify-content: center;
}`;
            } else if (comp.type === 'div' && comp.style?.display === 'flex') {
                styles += `
${selector} {
    display: flex !important;
}`;
            }
            
            // 递归处理子组件
            if (comp.children && comp.children.length > 0) {
                processComponentStyles(comp.children, `${selector} > `);
            }
        });
    };
    
    processComponentStyles(components);
    return styles;
}

/**
 * Generates the project files based on the design store state.
 */
export async function generateProjectFiles(): Promise<ExportedFile[]> {
    const designStore = useDesignStore();
    const outputFiles: ExportedFile[] = [];

    try {
        const preparedComponents = prepareComponentsForExport(designStore.canvasComponents);
        const componentUsage = getComponentUsage(designStore.canvasComponents);

        const templateDir = 'src/templates'; // Relative to project root where templates are

        // --- Data for templates ---
        const viewData = {
            components: preparedComponents,
            componentUsage: componentUsage,
            globalStyles: '/* Global styles placeholder */', // TODO: Process and include global styles
            projectName: 'my-generated-app', // TODO: Make configurable
            productName: 'My Generated App', // TODO: Make configurable
            windowWidth: 800, // TODO: Get from settings or canvas size
            windowHeight: 600, // TODO: Get from settings or canvas size
        };

        // --- Render templates ---
        const templatesToRender = [
            { template: 'MainWindow.vue.ejs', output: 'src/components/MainWindow.vue' },
            { template: 'main.js.ejs', output: 'src/main.js' },
            { template: 'index.html.ejs', output: 'index.html' },
            { template: 'electron_main.js.ejs', output: 'electron/main.js' },
            { template: 'package.json.ejs', output: 'package.json' },
        ];

        for (const { template, output } of templatesToRender) {
            // Node.js path functions don't work directly in Vite's frontend code.
            // We assume the templates are relative to the CWD or easily accessible.
            // In a real scenario, templates might be fetched or bundled differently.
            // For now, we simulate reading them (replace with actual read logic if needed).
            
            // **IMPORTANT:** In a real Electron app, reading templates would happen 
            // either in the main process or preload script, or templates would be 
            // bundled with the renderer code.
            // This direct path usage is likely conceptual for Vite dev environment.
            const templatePath = `${templateDir}/${template}`;
            console.log(`Attempting to render template: ${templatePath}`);

            // Fetch the template content (replace with actual file reading in Electron main/preload)
            let templateContent = '';
            try {
                // Example: Simulate fetch if running in browser context
                 const response = await fetch(`/src/templates/${template}`); // Relative to public/ or handled by dev server
                 if (!response.ok) throw new Error(`Failed to fetch template ${template}: ${response.statusText}`);
                 templateContent = await response.text();

                // In Electron Main process, you would use:
                // const fs = require('fs');
                // const path = require('path');
                // templateContent = fs.readFileSync(path.join(__dirname, '../renderer', templateDir, template), 'utf-8');
            } catch (fetchError) {
                console.error(`Error fetching/reading template ${template}:`, fetchError);
                 ElMessage.error(`无法加载模板文件: ${template}`);
                throw new Error(`Could not load template ${template}`); 
            }
            
            if (!templateContent) {
                 ElMessage.error(`模板文件为空: ${template}`);
                 throw new Error(`Template content is empty for ${template}`);
            }

            const renderedContent = ejs.render(templateContent, viewData, {
                // EJS options if needed
            });

            outputFiles.push({
                relativePath: output,
                content: renderedContent,
            });
        }

        console.log('Generated files data:', outputFiles);
        ElMessage.success('代码文件内容已生成！');
        return outputFiles;

    } catch (error) {
        console.error('Error generating project files:', error);
        ElMessage.error('生成代码文件时出错。');
        return []; // Return empty array on error
    }
}

// TODO: Add function to trigger download/saving (likely involving IPC to main process) 